package pl.un4giv3n.mightvsmagic.action;

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;

import javax.persistence.EntityManager;
import javax.persistence.EntityTransaction;

import pl.un4giv3n.mightvsmagic.entity.Action;
import pl.un4giv3n.mightvsmagic.entity.ActionType;
import pl.un4giv3n.mightvsmagic.entity.Item;
import pl.un4giv3n.mightvsmagic.entity.ItemTemplate;
import pl.un4giv3n.mightvsmagic.entity.ItemType;
import pl.un4giv3n.mightvsmagic.entity.User;
import pl.un4giv3n.mightvsmagic.utils.ActionUtil;
import pl.un4giv3n.mightvsmagic.utils.ItemUtil;

/**
 * @author andrzejewskia action showing bazar page
 * 
 */
public class BazarPageAction extends PersistenceAction {

	private static final long serialVersionUID = 1L;
	/**
	 * session user
	 */
	protected User user;
	/**
	 * items avaible on the bazar
	 */
	protected List<ItemTemplate> avaibleEq;
	protected List<ItemTemplate> swords = new ArrayList<ItemTemplate>();
	protected List<ItemTemplate> wands = new ArrayList<ItemTemplate>();
	protected List<ItemTemplate> armors = new ArrayList<ItemTemplate>();
	protected List<ItemTemplate> shields = new ArrayList<ItemTemplate>();
	protected List<ItemTemplate> rings = new ArrayList<ItemTemplate>();
	protected List<ItemTemplate> charms = new ArrayList<ItemTemplate>();
	protected List<Item> userSwords = new ArrayList<Item>();
	protected List<Item> userWands = new ArrayList<Item>();
	protected List<Item> userArmors = new ArrayList<Item>();
	protected List<Item> userShields = new ArrayList<Item>();
	protected List<Item> userRings = new ArrayList<Item>();
	protected List<Item> userCharms = new ArrayList<Item>();
	protected ItemType selectedType = ItemType.ARMOR;
	/**
	 * current action performed by user
	 */
	protected Action currentAction;
	/**
	 * user items for selling
	 */
	protected List<Item> userEq;

	/*
	 * (non-Javadoc)
	 * 
	 * @see pl.un4giv3n.mightvsmagic.action.PersistenceAction#execute()
	 */
	@Override
	public String execute() {
		EntityManager entityManager = getEntityManager();
		user = getSessionUser(entityManager);
		if (user == null) {
			addActionError("Zaloguj się");
			entityManager.close();
			return LOGIN;
		}
		prepareEq(entityManager);
		currentAction = user.getCurrentAction();
		if (currentAction != null
				&& currentAction.getActionType().equals(ActionType.FIGHT)) {
			if (ActionUtil.actionEnded(currentAction, user)) {
				EntityTransaction transaction = entityManager.getTransaction();
				transaction.begin();
				user.setCurrentAction(Action.NO_ACTION);
				entityManager.merge(user);
				entityManager.flush();
				transaction.commit();
				currentAction = Action.NO_ACTION;
			}
			entityManager.close();
			return SUCCESS;

		}
		entityManager.close();
		if (currentAction == null || currentAction.equals(Action.NO_ACTION)) {
			return SUCCESS;
		} else {
			addActionError(ActionUtil.generateErrorMessage(currentAction, user));
			return ERROR;
		}
	}

	/**
	 * retrive and prepare avaible eq for display
	 * @param entityManager
	 */
	protected void prepareEq(EntityManager entityManager) {
		avaibleEq = ItemUtil.getAvaibleEq(entityManager, user);
		userEq = user.getItems();
		dispatchEquipment();
		sort();
	}

	private void sort() {
		Collections.sort(shields);
		Collections.sort(armors);
		Collections.sort(wands);
		Collections.sort(swords);
		Collections.sort(rings);
		Collections.sort(charms);
		Collections.sort(userShields);
		Collections.sort(userArmors);
		Collections.sort(userWands);
		Collections.sort(userSwords);
		Collections.sort(userRings);
		Collections.sort(userCharms);
		
	}

	protected void dispatchEquipment() {
		dispatchAvaibleEq();
		dispatchUserEq();

	}

	private void dispatchUserEq() {
		for (Item item : userEq) {
			switch (item.getType()) {
			case SHIELD:
				userShields.add(item);
				break;
			case WAND1H:
			case WAND2H:
				userWands.add(item);
				break;
			case SWORD1H:
			case SWORD2H:
				userSwords.add(item);
				break;
			case ARMOR:
				userArmors.add(item);
				break;
			case RING:
				userRings.add(item);
				break;
			case CHARM:
				userCharms.add(item);
				break;
			}
		}
	}

	private void dispatchAvaibleEq() {
		for (ItemTemplate template : avaibleEq) {
			switch (template.getType()) {
			case SHIELD:
				shields.add(template);
				break;
			case WAND1H:
			case WAND2H:
				wands.add(template);
				break;
			case SWORD1H:
			case SWORD2H:
				swords.add(template);
				break;
			case ARMOR:
				armors.add(template);
				break;
			case RING:
				rings.add(template);
				break;
			case CHARM:
				charms.add(template);
				break;
			}
		}
	}

	/**
	 * @return action end time formated as string for javascript countdown
	 */
	public String getActionEndString() {
		return ActionUtil.getActionEndDate(currentAction, user);
	}

	public List<ItemTemplate> getSwords() {
		return swords;
	}

	public List<ItemTemplate> getWands() {
		return wands;
	}

	public List<ItemTemplate> getArmors() {
		return armors;
	}

	public List<ItemTemplate> getShields() {
		return shields;
	}

	public List<ItemTemplate> getRings() {
		return rings;
	}

	public List<ItemTemplate> getCharms() {
		return charms;
	}

	public ItemType getSelectedType() {
		return selectedType;
	}

	public void setSelectedType(String selectedType) {
		this.selectedType = ItemType.valueOf(selectedType);
	}

	public List<Item> getUserSwords() {
		return userSwords;
	}

	public List<Item> getUserWands() {
		return userWands;
	}

	public List<Item> getUserArmors() {
		return userArmors;
	}

	public List<Item> getUserShields() {
		return userShields;
	}

	public List<Item> getUserRings() {
		return userRings;
	}

	public List<Item> getUserCharms() {
		return userCharms;
	}
	
}
